React Hooks ライブラリ「SWR」の Bound Mutate を Next.js で試してみた
こんにちは!DA(データアナリティクス)事業本部 サービスソリューション部の大高です。
先日、データ取得のための React Hooks ライブラリ「SWR」をNext.jsで試してみました。
今回はこのライブラリのMutation機能の1つ、 Bound Mutate を試してみたいと思います。
そもそも「Mutation」とは?
Mutationとは、日本語で「変化」や「変更」を表す通り、データの更新を行うための仕組みです。
たとえばGraphQLにおいては、Mutationはデータの作成、更新、削除に利用されるそうです。
In GraphQL, mutations are used to create, update, or delete data.
SWRでは、自動でデータの再検証を行ってくれるのですが、これを手動で行いたい場合にmutate
関数を利用できます。「データの更新」のために利用できる関数ですね。
SWRのBound Mutate
SWRにはuseSWRConfig()
からmutate
関数を取得して呼び出す方法と、useSWR()
からmutate
関数を取得して呼び出す方法があります。
前者は呼び出し時にキーの文字列を指定して利用しますが、後者はuseSWR()
で既にキーを指定しているのでキーパラメータは不要となります。
公式サンプルを一部抜粋すると、前者の場合は以下のようなイメージで
const { mutate } = useSWRConfig() const { data } = useSWR('/api/user', fetcher) (...snip...) // ソースを更新するために API にリクエストを送信 await requestUpdateUsername(newName) (...snip...) // このキーを使用して再検証(再取得) mutate('/api/user')
後者の場合は以下のようなイメージで、こちらが「Bound Mutate」と呼ばれています。
const { data, mutate } = useSWR('/api/user', fetcher) (...snip...) // ソースを更新するために API にリクエストを送信 await requestUpdateUsername(newName) (...snip...) // ローカルデータをすぐに更新し、再検証(再フェッチ) mutate({ ...data, name: newName })
こちらの方は、useSWR
で指定したキーにバインドされているmutate
を利用しており、範囲が限定されています。
試してみる
実際に以下のようなコードをNext.jsで試してみます。
import type { NextPage } from "next"; import useSWR from "swr"; const getCookieVal = (key: string) => { let cookieVal = ((document.cookie + ";").match(key + "=([^¥S;]*)") || [])[1]; if (!cookieVal) { cookieVal = "[Empty]"; } return cookieVal; }; const clearCookieVal = (key: string) => { document.cookie = key + "=; max-age=0"; }; const SWRMutate: NextPage = () => { const { data, mutate } = useSWR("foo", getCookieVal, { revalidateOnFocus: false, }); const updateCookieVal = (key: string, val: string) => { document.cookie = key + "=" + encodeURIComponent(val); mutate(val); }; return ( <div> <h2>{data}</h2> <button onClick={() => updateCookieVal("foo", "bar")}>Set Cookie</button> <button onClick={() => clearCookieVal("foo")}>Clear Cookie</button> </div> ); }; export default SWRMutate;
このコードでは、Cookieのキーfoo
に対してデータ取得を行い、画面に表示しています。
Cookieにデータが存在しなかった場合には[Empty]
という値を返して表示し、「Set Cookie」ボタンでbar
という値を設定、「Clear Cookie」ボタンで値をクリアします。
また、「Set Cookie」ボタンクリック時のイベントではmutate
を呼び出してデータ反映を行います。一方で、「Clear Cookie」ボタンのイベントではmutate
は呼び出さずに、データ反映を行わないようにしています。
なお、今回のuseSWR
の呼び出しにおいてはフォーカス変更時に自動で再検証がされると挙動が分かりづらいので、revalidateOnFocus
をfalse
にすることで再検証がされないようにしています。
初期状態
実際に動かすと、初期状態はこのような感じです。
Cookieが空なので[Empty]
という値が表示されています。
mutateの呼び出し
次に「Set Cookie」ボタンをクリックします。
Cookieが設定されて、mutate
が呼び出されたのでbar
が表示されました。
mutateを呼び出さない場合
最後に「Clear Cookie」ボタンをクリックします。
Cookieがクリアされましたが、今度はmutate
を呼び出していないので画面はそのままbar
になっていることが分かります。
まとめ
以上、React Hooks ライブラリ「SWR」のBound Mutateを試してみました。
SWRには様々な自動再検証機能があるのですが、検証タイミングを自分で制御したいケースではmutateを活用できると良さそうですね。
どなたかのお役に立てば幸いです。それでは!